package com.ruoyi.zhgd.service.impl;

import cn.hutool.core.bean.BeanUtil;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.ruoyi.common.exception.ServiceException;
import com.ruoyi.common.utils.DateUtils;
import com.ruoyi.common.utils.StringUtils;
import com.baomidou.dynamic.datasource.annotation.DS;
import com.ruoyi.common.core.page.TableDataInfo;
import com.ruoyi.common.core.domain.PageQuery;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.ruoyi.zhgd.domain.NLaboratoryAsphaltRequiresRef;
import com.ruoyi.zhgd.dto.AsphaltRequiresDto;
import com.ruoyi.zhgd.dto.AsphaltRequiresRefDto;
import com.ruoyi.zhgd.dto.AsphaltRequiresRefRHDDto;
import com.ruoyi.zhgd.dto.AsphaltRequiresRefYDDto;
import com.ruoyi.zhgd.mapper.NLaboratoryAsphaltRequiresRefMapper;
import com.ruoyi.zhgd.service.INLaboratoryAsphaltRequiresRefService;
import lombok.RequiredArgsConstructor;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import com.ruoyi.zhgd.domain.bo.NLaboratoryAsphaltRequiresBo;
import com.ruoyi.zhgd.domain.vo.NLaboratoryAsphaltRequiresVo;
import com.ruoyi.zhgd.domain.NLaboratoryAsphaltRequires;
import com.ruoyi.zhgd.mapper.NLaboratoryAsphaltRequiresMapper;
import com.ruoyi.zhgd.service.INLaboratoryAsphaltRequiresService;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;


import java.util.*;
import java.util.stream.Collectors;

/**
 * 沥青技术要求详情Service业务层处理
 *
 * @author cj
 * @date 2023-09-21
 */
@RequiredArgsConstructor
@Service
@DS("sjcj")
public class NLaboratoryAsphaltRequiresServiceImpl implements INLaboratoryAsphaltRequiresService {

    private final NLaboratoryAsphaltRequiresMapper baseMapper;

    @Autowired
    private NLaboratoryAsphaltRequiresRefMapper requiresRefMapper;

    @Autowired
    private INLaboratoryAsphaltRequiresRefService requiresRefService;

    /**
     * 查询沥青技术要求详情
     */
    @Override
    public AsphaltRequiresDto queryById(String id){
        AsphaltRequiresDto asphaltRequiresDto = new AsphaltRequiresDto();

        NLaboratoryAsphaltRequires nLaboratoryAsphaltRequires = baseMapper.selectById(id);
        String type = "YD";
        String typeZ = "ZRD";
        String typeR = "RHD";
        List<AsphaltRequiresRefDto> nLaboratoryAsphaltRequiresRefs = baseMapper.selectDetail(id,typeZ);
        List<AsphaltRequiresRefYDDto> asphaltRequiresRefYDDtos = baseMapper.selectDetailYD(id, type);
        List<AsphaltRequiresRefRHDDto> asphaltRequiresRefRHDDtoList = baseMapper.selectDetailRHD(id, typeR);
        BeanUtils.copyProperties(nLaboratoryAsphaltRequires,asphaltRequiresDto);
        asphaltRequiresDto.setRefs(nLaboratoryAsphaltRequiresRefs);
        asphaltRequiresDto.setRhdRefs(asphaltRequiresRefRHDDtoList);
        asphaltRequiresDto.setYdRefs(asphaltRequiresRefYDDtos);
        return asphaltRequiresDto;
    }

    /**
     * 查询沥青技术要求详情列表
     */
    @Override
    public TableDataInfo<NLaboratoryAsphaltRequiresVo> queryPageList(NLaboratoryAsphaltRequiresBo bo, PageQuery pageQuery) {
        LambdaQueryWrapper<NLaboratoryAsphaltRequires> lqw = buildQueryWrapper(bo);
        Page<NLaboratoryAsphaltRequiresVo> result = baseMapper.selectVoPage(pageQuery.build(), lqw);
        return TableDataInfo.build(result);
    }

    /**
     * 查询沥青技术要求详情列表
     */
    @Override
    public List<NLaboratoryAsphaltRequiresVo> queryList(NLaboratoryAsphaltRequiresBo bo) {
        LambdaQueryWrapper<NLaboratoryAsphaltRequires> lqw = buildQueryWrapper(bo);
        return baseMapper.selectVoList(lqw);
    }

    private LambdaQueryWrapper<NLaboratoryAsphaltRequires> buildQueryWrapper(NLaboratoryAsphaltRequiresBo bo) {
        Map<String, Object> params = bo.getParams();
        LambdaQueryWrapper<NLaboratoryAsphaltRequires> lqw = Wrappers.lambdaQuery();
        lqw.like(StringUtils.isNotBlank(bo.getName()), NLaboratoryAsphaltRequires::getName, bo.getName());
        lqw.eq(StringUtils.isNotBlank(bo.getType()), NLaboratoryAsphaltRequires::getType, bo.getType());
        lqw.eq(StringUtils.isNotBlank(bo.getInsertBy()), NLaboratoryAsphaltRequires::getInsertBy, bo.getInsertBy());
        lqw.eq(bo.getInsertTime() != null, NLaboratoryAsphaltRequires::getInsertTime, bo.getInsertTime());
        lqw.eq(StringUtils.isNotBlank(bo.getDeleted()), NLaboratoryAsphaltRequires::getDeleted, bo.getDeleted());
        lqw.eq(StringUtils.isNotBlank(bo.getSoftDesc()), NLaboratoryAsphaltRequires::getSoftDesc, bo.getSoftDesc());
        lqw.eq(StringUtils.isNotBlank(bo.getPenetration()), NLaboratoryAsphaltRequires::getPenetration, bo.getPenetration());
        lqw.eq(StringUtils.isNotBlank(bo.getDuctility()), NLaboratoryAsphaltRequires::getDuctility, bo.getDuctility());
        lqw.eq(StringUtils.isNotBlank(bo.getDeptId()), NLaboratoryAsphaltRequires::getDeptId, bo.getDeptId());
        lqw.eq(StringUtils.isNotBlank(bo.getDeptPkid()), NLaboratoryAsphaltRequires::getDeptPkid, bo.getDeptPkid());
        return lqw;
    }

    /**
     * 新增沥青技术要求详情
     */
    @Override
    public Boolean insertByBo(NLaboratoryAsphaltRequiresBo bo) {
        NLaboratoryAsphaltRequires add = BeanUtil.toBean(bo, NLaboratoryAsphaltRequires.class);
        validEntityBeforeSave(add);
        boolean flag = baseMapper.insert(add) > 0;
        if (flag) {
            bo.setId(add.getId());
        }
        return flag;
    }

    /**
     * 修改沥青技术要求详情
     */
    @Override
    public Boolean updateByBo(NLaboratoryAsphaltRequiresBo bo) {
        NLaboratoryAsphaltRequires update = BeanUtil.toBean(bo, NLaboratoryAsphaltRequires.class);
        validEntityBeforeSave(update);
        return baseMapper.updateById(update) > 0;
    }

    /**
     * 保存前的数据校验
     */
    private void validEntityBeforeSave(NLaboratoryAsphaltRequires entity){
        //TODO 做一些数据校验,如唯一约束
    }

    /**
     * 批量删除沥青技术要求详情
     */
    @Override
    public Boolean deleteWithValidByIds(Collection<String> ids, Boolean isValid) {
        if(isValid){
            //TODO 做一些业务上的校验,判断是否需要校验
        }
        return baseMapper.deleteBatchIds(ids) > 0;
    }

    /**
     * xinzeng
     * @param dto
     */
    @Transactional(rollbackFor = Exception.class)
    @Override
    public void saveRequires(AsphaltRequiresDto dto) {
        QueryWrapper<NLaboratoryAsphaltRequires> query = new QueryWrapper<>();
        query.eq("deleted","0").eq("name",dto.getAsphaltVariety()+dto.getAsphaltLabel());
        query.ne(StringUtils.isNotBlank(dto.getId()),"id",dto.getId());
        Long result = baseMapper.selectCount(query);
        if(result > 0){
            throw new ServiceException("名称"+dto.getName()+"的技术要求已经存在，请重新输入！");
        }
        NLaboratoryAsphaltRequires entity = new NLaboratoryAsphaltRequires();
        BeanUtils.copyProperties(dto,entity);
        entity.setName(dto.getAsphaltVariety()+dto.getAsphaltLabel());
        entity.setInsertTime(DateUtils.getNowDate());
        entity.setDeleted("0");
        if(StringUtils.isNotBlank(entity.getId())){
            baseMapper.updateById(entity);
        }else{
            baseMapper.insert(entity);
        }
        this.insertRequiresRef(entity.getId(),dto);
    }

    /**
     * 修改
     * @param dto
     */
    @Override
    public void updateRequires(AsphaltRequiresDto dto) {
        NLaboratoryAsphaltRequires requires = new NLaboratoryAsphaltRequires();
        BeanUtils.copyProperties(dto,requires);
        //数据库原有数据
        NLaboratoryAsphaltRequires asphaltRequires = baseMapper.selectById(dto.getId());
        if (dto.getAsphaltLabel() != asphaltRequires.getAsphaltLabel() || dto.getAsphaltVariety() != asphaltRequires.getAsphaltVariety()){
            requires.setName(dto.getAsphaltVariety()+dto.getAsphaltLabel());
        }
        requires.setUpdateTime(DateUtils.getNowDate());
        baseMapper.updateById(requires);
        //处理详情表
        QueryWrapper<NLaboratoryAsphaltRequiresRef> wrapper = new QueryWrapper<>();
        wrapper.eq("asphalt_id",requires.getId());
        List<NLaboratoryAsphaltRequiresRef> asphaltRequiresRefs = requiresRefMapper.selectList(wrapper);
        for (NLaboratoryAsphaltRequiresRef requiresRef : asphaltRequiresRefs) {
            requiresRefMapper.updateByAsphaltId(requiresRef.getId());
        }
        insertOrUpdarte(requires.getId(),dto);
    }

    private void insertRequiresRef(String id, AsphaltRequiresDto dto) {
        QueryWrapper<NLaboratoryAsphaltRequiresRef> deleteWrap = new QueryWrapper<>();
        deleteWrap.eq("asphalt_id",id);
        requiresRefMapper.delete(deleteWrap);
        insertOrUpdarte(id,dto);
    }

    private void insertOrUpdarte(String id,AsphaltRequiresDto dto){
        UUID randomed = UUID.randomUUID();
        if(!CollectionUtils.isEmpty(dto.getRefs())){
            List<NLaboratoryAsphaltRequiresRef> list = dto.getRefs().stream().map(ref -> {
                ref.setAsphaltId(id);
                NLaboratoryAsphaltRequiresRef re = new NLaboratoryAsphaltRequiresRef();
                BeanUtils.copyProperties(ref,re);
                re.setType("ZRD");
                return re;
            }).collect(Collectors.toList());
            requiresRefMapper.insertBatch(list);
        }
        if(!CollectionUtils.isEmpty(dto.getYdRefs())){
            List<AsphaltRequiresRefYDDto> ydRefs = dto.getYdRefs();
            for (AsphaltRequiresRefYDDto ydRef : ydRefs) {
                NLaboratoryAsphaltRequiresRef re = new NLaboratoryAsphaltRequiresRef();
                NLaboratoryAsphaltRequiresRef re1 = new NLaboratoryAsphaltRequiresRef();
                if (ydRef.getMin1() != null ){
                    //延度
                    re1.setAsphaltId(id);
                    re1.setMin(ydRef.getMin1());
                    re1.setIndicator(2);
                    re1.setCorrelation(String.valueOf(randomed));
                    re1.setType("YD");
                    requiresRefMapper.insert(re1);
                }
                if (ydRef.getMin() != null  || ydRef.getTemperature() != null){
                    re.setAsphaltId(id);
                    //温度
                    re.setMin(ydRef.getMin());
                    re.setTemperature(ydRef.getTemperature());
                    re.setIndicator(1);
                    re.setCorrelation(String.valueOf(randomed));
                    re.setType("YD");
                    requiresRefMapper.insert(re);
                }
            }
        }
        if(!CollectionUtils.isEmpty(dto.getRhdRefs())){
            List<NLaboratoryAsphaltRequiresRef> list = dto.getRhdRefs().stream().map(ref -> {
                NLaboratoryAsphaltRequiresRef re = new NLaboratoryAsphaltRequiresRef();
                ref.setAsphaltId(id);
                BeanUtils.copyProperties(ref,re);
                re.setType("RHD");
                return re;
            }).collect(Collectors.toList());
            requiresRefMapper.insertBatch(list);
        }
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public void removeRequires(String id) {
        QueryWrapper<NLaboratoryAsphaltRequiresRef> deleteWrap = new QueryWrapper<>();
        deleteWrap.eq("asphalt_id",id);
        requiresRefMapper.delete(deleteWrap);
        baseMapper.deleteById(id);
    }


    @Override
    public List<NLaboratoryAsphaltRequires> selectList(String type) {
        List<NLaboratoryAsphaltRequires> list = baseMapper.selectLists(type);
        return list;
    }

}
